#!/usr/bin/env python
# -*- coding: utf-8 -*-
# author:Charles.chen
# createDate:2017/9/5
# Title:
# Tip:
from apscheduler.schedulers.background import BackgroundScheduler
from app.model import Sensor, SensorData
import logging, os
import random
import time

logging.basicConfig()
# 定时任务总控制器
# Quartz实现单例模式 防止在更改任务周期时出现重复任务
# http://quanjie.leanote.com/post/Python%E4%BB%BB%E5%8A%A1%E8%B0%83%E5%BA%A6%E6%A8%A1%E5%9D%97-%E2%80%93-APScheduler-2
# self.sched.add_job(recordSystemInfo, 'interval', seconds=int(system_job_time), id=recordSystemInfo.func_name,
#                    max_instances=10)


class Quartz(object):
    sched = None
    __instance = None

    def __init__(self):
        if self.sched is None:
            # 手动设置时区 避免在openWrt环境下报错
            self.sched = BackgroundScheduler(gconfig={'timezone': 'Asia/Shanghai'}, prefix=None)
        pass

    def __new__(cls, *args, **kwargs):
        if Quartz.__instance is None:
            Quartz.__instance = object.__new__(cls, *args, **kwargs)
        return Quartz.__instance

    # 动态添加默认的定时任务
    def addJobDynamic(self):
        from app.crontime import crontimeService
        # TODO 获取传感器数据服务

        # 传感器数据推送服务
        self.sched.add_job(crontimeService.syncPushDataJob, 'interval', seconds=int(1), id="syncPushData",
                           max_instances=20)

        # sd卡检测服务，监测存储是否已经溢出警戒线 180S一次
        self.sched.add_job(crontimeService.monitorTFJob, 'interval', seconds=int(180), id="monitorTF",
                           max_instances=1)
        self.sched.pause_job("monitorTF")

        # 在tf卡内存溢出的情况下，数据库定时删除任务 15s一次
        self.sched.add_job(crontimeService.clearSensorDataJob, 'interval', seconds=int(15), id="clearSensorData",
                           max_instances=2)
        # 默认暂停任务
        self.sched.pause_job("clearSensorData")

        # 数据推送失败次数检测服务
        self.sched.add_job(crontimeService.checkSensorDataJob, 'interval', seconds=int(60), id="checkSensorData",
                           max_instances=2)
        # 默认暂停服务
        self.sched.pause_job("checkSensorData")

        # 网络链接再请求服务 60S一次 根据返回的结果 重置推送数据偏移量
        self.sched.add_job(crontimeService.applyNetworkCheckJob, 'interval', seconds=int(60), id="applyNetworkCheck",
                           max_instances=2)
        self.sched.pause_job("applyNetworkCheck")

        # 数据库备份服务 一天一次
        self.sched.add_job(crontimeService.backUpSensorDataJob, 'cron', hour=1, minute=30, id="backUpSensorData",
                           max_instances=1)

        # 配置文件备份服务 一天一次
        self.sched.add_job(crontimeService.backUpConfigJob, 'cron', hour=1, minute=10, id="backUpConfig",
                           max_instances=1)
        pass

    # 开始任务
    def startJob(self):
        self.sched.start()


    # 动态移除定时任务
    def removeJobDynamic(self):
        self.sched.pause()
        self.sched.remove_job()
        self.sched.resume()
        pass

    # 动态修改定时任务的发生周期
    def updateJobTimeForSensor(self, job_name=None, job_time=None, sensor_no=None):
        self.sched.pause()
        # remove Invalid job
        self.removeJob(str(sensor_no))
        # add new job
        self.sched.add_job(getattr(sensorQuartz, job_name), 'interval', seconds=int(job_time), id=str(sensor_no))
        # continue job
        self.sched.resume()
        pass

    # 同时暂停一个任务和开启一个任务
    def stopAndStartJob(self, stopJobId=None, startJobId=None):
        # 恢复一个任务
        self.sched.resume_job(startJobId)
        # 暂定一个任务
        self.sched.pause_job(stopJobId)
        pass

def getSensorDataTest():
    insert_data = {
        "sensor_no": "sensor001",
        "param_name": "测试用数据",
        "val": random.randint(0, 100),
        "created_time": time.time(),
        "is_post": False,
        "timestamp": time.time()
        }
    SensorData.insert(insert_data).execute()
    print "running getSensorDataTest over"
    pass



if __name__ == '__main__':
    s1 = Quartz()
    s2 = Quartz()
    print id(s1.sched)
    print id(s2.sched)

    pass

